home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Aminet 24
/
Aminet 24 (1998)(GTI - Schatztruhe)[!][Apr 1998].iso
/
Aminet
/
comm
/
mail
/
Mutt089src.lha
/
Mutt-0.89i-AMIGA
/
src
/
curs_main.c
< prev
next >
Wrap
C/C++ Source or Header
|
1998-01-28
|
31KB
|
1,404 lines
/*
* Copyright (C) 1996-8 Michael R. Elkins <me@cs.hmc.edu>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "mutt.h"
#include "mutt_curses.h"
#include "mutt_menu.h"
#include "mailbox.h"
#include "sort.h"
#ifdef _PGPPATH
#include "pgp.h"
#endif
#include <ctype.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>
#include <string.h>
#include <sys/stat.h>
#include <errno.h>
#define CHECK_MSGCOUNT if (!Context) \
{ \
mutt_flushinp (); \
mutt_error ("No mailbox is open."); \
break; \
} \
else if (!Context->msgcount) \
{ \
mutt_flushinp (); \
mutt_error ("There are no messages."); \
break; \
}
#define CHECK_READONLY if (Context->readonly) \
{ \
mutt_flushinp (); \
mutt_error ("Mailbox is read-only."); \
break; \
}
#define CURHDR Context->hdrs[Context->v2r[menu->current]]
#define OLDHDR Context->hdrs[Context->v2r[menu->oldcurrent]]
void index_make_entry (char *s, size_t l, MUTTMENU *menu, int num)
{
int flag = 0;
HEADER *h = Context->hdrs[Context->v2r[num]];
if ((Sort & SORT_MASK) == SORT_THREADS &&
Context->msgcount == Context->vcount &&
h->tree)
{
if (h->display_subject)
flag = M_FORCESUBJ;
else if (Sort & SORT_REVERSE)
{
if ((h->parent->msgno > menu->top + menu->pagelen - 1) &&
(!h->prev || (h->prev->msgno > menu->top + menu->pagelen - 1)))
flag = M_FORCESUBJ;
}
else if ((h->parent->msgno < menu->top) &&
(!h->prev || (h->prev->msgno < menu->top)))
flag = M_FORCESUBJ;
flag |= M_TREE; /* display the thread tree */
}
_mutt_make_string (s, l, HdrFmt, h, flag);
}
static int ci_next_undeleted (int msgno)
{
int i;
for (i=msgno+1; i < Context->vcount; i++)
if (! Context->hdrs[Context->v2r[i]]->deleted)
return (i);
return (-1);
}
static int ci_previous_undeleted (int msgno)
{
int i;
for (i=msgno-1; i>=0; i--)
if (! Context->hdrs[Context->v2r[i]]->deleted)
return (i);
return (-1);
}
/* Return the index of the first new message, or failing that, the first
* unread message.
*/
static int ci_first_message (void)
{
int old = -1, i;
if (Context && Context->msgcount)
{
for (i=0; i < Context->vcount; i++)
{
if (! Context->hdrs[Context->v2r[i]]->read &&
! Context->hdrs[Context->v2r[i]]->deleted)
{
if (! Context->hdrs[Context->v2r[i]]->old)
return (i);
else if (old == -1)
old = i;
}
}
if (old != -1)
return (old);
/* If Sort is reverse and not threaded, the latest message is first.
* If Sort is threaded, the latest message is first iff exactly one
* of Sort and SortAux are reverse.
*/
if (((Sort & SORT_REVERSE) && (Sort & SORT_MASK) != SORT_THREADS) ||
((Sort & SORT_MASK) == SORT_THREADS &&
((Sort ^ SortAux) & SORT_REVERSE)))
return 0;
else
return (Context->vcount ? Context->vcount - 1 : 0);
}
return 0;
}
/* This should be in mx.c, but it only gets used here. */
static int mx_toggle_write (CONTEXT *ctx)
{
if (!ctx)
return -1;
if (ctx->readonly)
{
mutt_error ("Cannot toggle write on a readonly mailbox!");
return -1;
}
if (ctx->dontwrite)
{
ctx->dontwrite = 0;
mutt_message ("Changes to folder will be written on folder exit.");
}
else
{
ctx->dontwrite = 1;
mutt_message ("Changes to folder will not be written.");
}
return 0;
}
/* This function handles the message index window as well as commands returned
* from the pager (MENU_PAGER).
*/
void mutt_index_menu (void)
{
char buf[LONG_STRING], helpstr[SHORT_STRING];
int op = OP_NULL; /* function to execute */
int done = 0; /* controls when to exit the "event" loop */
int i = 0, j;
int tag = 0; /* has the tag-prefix command been pressed? */
int newcount = -1;
int oldcount = -1;
int rc = -1;
MUTTMENU *menu;
char *cp; /* temporary variable. */
int index_hint; /* used to restore cursor position */
menu = mutt_new_menu ();
menu->menu = MENU_MAIN;
menu->offset = 1;
menu->pagelen = LINES - 3;
menu->make_entry = index_make_entry;
menu->current = ci_first_message ();
helpstr[0] = 0;
mutt_make_help (buf, sizeof (buf), "Quit ", MENU_MAIN, OP_QUIT);
strcat (helpstr, buf);
mutt_make_help (buf, sizeof (buf), "Del ", MENU_MAIN, OP_DELETE);
strcat (helpstr, buf);
mutt_make_help (buf, sizeof (buf), "Undel ", MENU_MAIN, OP_UNDELETE);
strcat (helpstr, buf);
mutt_make_help (buf, sizeof (buf), "Save ", MENU_MAIN, OP_SAVE);
strcat (helpstr, buf);
mutt_make_help (buf, sizeof (buf), "Mail ", MENU_MAIN, OP_MAIL);
strcat (helpstr, buf);
mutt_make_help (buf, sizeof (buf), "Reply ", MENU_MAIN, OP_REPLY);
strcat (helpstr, buf);
mutt_make_help (buf, sizeof (buf), "Group ", MENU_MAIN, OP_GROUP_REPLY);
strcat (helpstr, buf);
mutt_make_help (buf, sizeof (buf), "Help", MENU_MAIN, OP_HELP);
strcat (helpstr, buf);
menu->help = helpstr;
FOREVER
{
tag = 0; /* clear the tag-prefix */
menu->max = Context ? Context->vcount : 0;
oldcount = Context ? Context->msgcount : 0;
if (Context)
{
/* check for new mail in the mailbox. If nonzero, then something has
* changed about the file (either we got new mail or the file was
* modified underneath us.)
*/
index_hint = (Context->vcount) ? CURHDR->index : 0;
if ((i = mx_check_mailbox (Context, &index_hint)) < 0)
{
if (!Context->path)
{
/* fatal error occurred */
safe_free ((void **) &Context);
menu->redraw = REDRAW_FULL;
}
set_option (OPTSEARCHINVALID);
}
else if (i > 0)
{
/* take note of the current message */
if (oldcount)
{
if (menu->current < Context->vcount)
menu->oldcurrent = index_hint;
else
oldcount = 0; /* invalid message number! */
}
/* if the mailbox was reopened, need to rethread from scratch */
mutt_sort_headers (Context, (i == M_REOPENED));
menu->current = -1;
if (oldcount)
{
int j;
/* restore the current message to the message it was pointing to */
for (j = 0; j < Context->vcount; j++)
if (Context->hdrs[Context->v2r[j]]->index == menu->oldcurrent)
{
menu->current = j;
break;
}
}
if (menu->current < 0)
menu->current = ci_first_message ();
/* notify the user of new mail */
if (i == M_REOPENED)
mutt_error ("Mailbox was externally modified. Flags may be wrong.");
else
mutt_message ("New mail in this mailbox.");
menu->redraw = REDRAW_FULL;
menu->max = Context->vcount;
set_option (OPTSEARCHINVALID);
}
}
/* check for new mail in the incoming folders */
oldcount = newcount;
if ((newcount = mutt_buffy_check ()) != oldcount)
menu->redraw |= REDRAW_STATUS;
mutt_buffy_notify ();
mutt_curs_set (0);
if (menu->redraw & REDRAW_FULL)
{
menu_redraw_full (menu);
mutt_show_error ();
}
if (menu->redraw & REDRAW_STATUS)
{
mutt_status_line (buf, sizeof (buf), Status);
CLEARLINE (option (OPTSTATUSONTOP) ? 0 : LINES-2);
SETCOLOR (MT_COLOR_STATUS);
printw ("%-*.*s", COLS, COLS, buf);
SETCOLOR (MT_COLOR_NORMAL);
menu->redraw &= ~REDRAW_STATUS;
}
if (menu->menu == MENU_MAIN)
{
if (Context)
{
menu_check_recenter (menu);
if (menu->redraw == REDRAW_INDEX)
menu_redraw_index (menu);
else if (menu->redraw & (REDRAW_MOTION_RESYNCH |